package com.luofan.service.impl;

import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.luofan.common.constant.RoleConstant;
import com.luofan.common.result.CustomException;
import com.luofan.common.result.ResultCodeEnum;
import com.luofan.common.util.UserContext;
import com.luofan.entity.dto.ArchiveQueryDTO;
import com.luofan.entity.dto.StatisticsDTO;
import com.luofan.entity.po.Archive;
import com.luofan.entity.vo.ArchiveVO;
import com.luofan.entity.vo.StatisticsVO;
import com.luofan.mapper.ArchiveMapper;
import com.luofan.mapper.CollectMapper;
import com.luofan.service.ArchiveService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.List;

/**
 * <p>
 * 档案表 服务实现类
 * </p>
 *
 * @author 
 * @since 2025-03-26
 */
@Service
public class ArchiveServiceImpl extends ServiceImpl<ArchiveMapper, Archive> implements ArchiveService {

    @Autowired
    private ArchiveMapper archiveMapper;
    @Autowired
    private CollectMapper collectMapper;

    //教师上传档案
    @Override
    @Transactional
    public ResultCodeEnum saveArchiveByCollectId(Archive archive) {
        LocalDateTime now = LocalDateTime.now();
        //设置当前时间为上传时间
        archive.setUploadTime(now);

        //根据档案收集任务id获取最晚完成时间
        LocalDateTime completionTime = collectMapper.getCompletionTimeById(archive.getCollectId());
        //如果当前时间晚于档案收集任务的最晚完成时间，则将档案状态设置为逾期
        if (now.isAfter(completionTime)) {
            archive.setIsOverdue(1);
        }
        //将档案状态设置为待审核
        archive.setStatus(1);

        //判断是否提交过此档案，如果提交过则修改，如果没有提交过则插入
        int count = archiveMapper.countByCollectIdAndUserId(archive.getCollectId(), archive.getUserId());

        if (count > 0) {
            //修改原有档案信息
            int rows = archiveMapper.updateArchive(archive, archive.getCollectId(), archive.getUserId());
            if (rows == 0) throw new CustomException(ResultCodeEnum.UPDATE_ERROR);
        } else {
            //插入档案信息
            int rows1 = archiveMapper.insert(archive);
            if (rows1 == 0) throw new CustomException(ResultCodeEnum.SAVE_ERROR);
        }

        //将档案设置为已提交
        int rows2 = archiveMapper.updateStatusById(archive.getCollectId(), archive.getUserId());
        if (rows2 == 0) throw new CustomException(ResultCodeEnum.SAVE_ERROR);

        return ResultCodeEnum.SUCCESS;
    }

    //教师修改档案(已通过审核不能修改)
    @Override
    public ResultCodeEnum updateArchiveById(Archive archive) {
        return archiveMapper.updateArchiveById(archive);
    }

    //根据档案收集任务id和用户id获取档案信息
    @Override
    public ArchiveVO getArchiveByCollectIdAndUserId(Long collectId, Long userId) {
        return archiveMapper.getArchiveByCollectIdAndUserId(collectId, userId);
    }

    //教研室主任 审核档案(审核通过需要评分)
    @Override
    public ResultCodeEnum checkArchive(Archive archive) {
        //获取当前用户id为审核者id
        archive.setVerifierId(UserContext.getCurrentUserId());

        //教研室主任 审核档案
        int rows = archiveMapper.checkArchive(archive);
        if (rows == 0) return ResultCodeEnum.FAIL;

        return ResultCodeEnum.SUCCESS;
    }

    //根据条件 分页获取档案信息
    @Override
    public PageInfo<ArchiveVO> listArchiveByCondition(ArchiveQueryDTO archiveQueryDTO) {
        //获取用户权限
        Byte currentRole = UserContext.getCurrentRole();
        //如果是教研室主任 将教研室id添加到查询条件
        if (currentRole == RoleConstant.HEAD) {
            archiveQueryDTO.setSectionId(UserContext.getCurrentSectionId());
        }
        //如果是教师 将用户id添加到查询条件
        if (currentRole == RoleConstant.TEACHER) {
            archiveQueryDTO.setUserId(UserContext.getCurrentUserId());
        }

        //进行分页拦截
        PageHelper.startPage(archiveQueryDTO.getPageNum(), archiveQueryDTO.getPageSize());
        //查询
        List<ArchiveVO> archiveVOList = archiveMapper.listArchiveByCondition(archiveQueryDTO);
        //获取PageInfo
        PageInfo<ArchiveVO> pageInfo = new PageInfo<>(archiveVOList);

        return pageInfo;
    }

    //根据所有档案的提交所需时间，是否逾期提交，质量评分 计算平均提交所需时间，逾期提交率，平均质量评分
    private StatisticsVO getAverage(List<StatisticsDTO> statisticsDTOList) {
        //获取平均提交所需时间，逾期提交率，平均质量评分
        double averageTime = 0;   //平均提交所需时间(小时)
        double overdueRate = 0;   //逾期提交率(百分比)
        double averageScore = 0;  //平均质量评分
        for (StatisticsDTO statisticsDTO : statisticsDTOList) {
            averageTime += statisticsDTO.getConsumeTime();
            overdueRate += statisticsDTO.getIsOverdue();
            averageScore += statisticsDTO.getScore();
        }
        averageTime /= statisticsDTOList.size();
        overdueRate /= statisticsDTOList.size();
        averageScore /= statisticsDTOList.size();

        averageTime /= 60;  //将分钟转换为小时

        //保留小数点后两位
        averageTime = Math.round(averageTime * 100) / 100.0;
        overdueRate = Math.round(overdueRate * 100) / 100.0;
        averageScore = Math.round(averageScore * 100) / 100.0;

        //将数据封装到StatisticsVO中并返回
        StatisticsVO statisticsVO = new StatisticsVO();
        statisticsVO.setAverageTime(averageTime);
        statisticsVO.setOverdueRate(overdueRate * 100);  //overdueRate为百分比，需要乘以100
        statisticsVO.setAverageScore(averageScore);

        return statisticsVO;
    }

    //根据教师id 获取档案的平均提交所需时间，逾期提交率，平均质量评分
    @Override
    public StatisticsVO statisticsByUserId(Long userId) {
        //根据教师id获取其每个所属档案的提交所需时间，是否逾期提交，质量评分
        List<StatisticsDTO> statisticsDTOList = archiveMapper.statisticsByUserId(userId);

        //根据所有档案的提交所需时间，是否逾期提交，质量评分 计算平均提交所需时间，逾期提交率，平均质量评分
        return getAverage(statisticsDTOList);
    }

    //根据档案收集任务id 获取档案的平均提交所需时间，逾期提交率，平均质量评分
    @Override
    public StatisticsVO statisticsByCollectId(Long collectId) {
        //根据档案收集任务id获取其每个所属档案的提交所需时间，是否逾期提交，质量评分
        List<StatisticsDTO> statisticsDTOList = archiveMapper.statisticsByCollectId(collectId);

        //根据所有档案的提交所需时间，是否逾期提交，质量评分 计算平均提交所需时间，逾期提交率，平均质量评分
        return getAverage(statisticsDTOList);
    }

    //根据教研室id和学期id 获取档案的平均提交所需时间，逾期提交率，平均质量评分
    @Override
    public StatisticsVO statisticsBySectionIdAndTermId(Long sectionId, Long termId) {
        //根据教研室id和学期id获取其每个所属档案的提交所需时间，是否逾期提交，质量评分
        List<StatisticsDTO> statisticsDTOList = archiveMapper.statisticsBySectionIdAndTermId(sectionId, termId);

        //根据所有档案的提交所需时间，是否逾期提交，质量评分 计算平均提交所需时间，逾期提交率，平均质量评分
        return getAverage(statisticsDTOList);
    }

    //根据学期id 获取档案的平均提交所需时间，逾期提交率，平均质量评分
    @Override
    public StatisticsVO statisticsByTermId(Long termId) {
        //根据学期id获取其每个所属档案的提交所需时间，是否逾期提交，质量评分
        List<StatisticsDTO> statisticsDTOList = archiveMapper.statisticsByTermId(termId);

        //根据所有档案的提交所需时间，是否逾期提交，质量评分 计算平均提交所需时间，逾期提交率，平均质量评分
        return getAverage(statisticsDTOList);
    }

}
